home *** CD-ROM | disk | FTP | other *** search
- #include "tear.h"
- #include "wdef.h"
-
- enum
- {
- kSplitWidth = 16
- };
-
- enum
- {
- kOurWDEFSignature = 'RSGM'
- };
-
- #ifdef powerc
- #pragma options align=mac68k
- #endif
-
- typedef struct
- {
- SInt16 bsr;
- UInt32 addr;
- SInt16 pop;
- SInt16 fetch;
- SInt16 jmp;
-
- UInt32 signature;
- Handle old_wdef;
- } defproc, **defproc_handle;
-
- #ifdef powerc
- #pragma options align=reset
- #endif
-
- static defproc default_dp = {
- 0x6104, // bsr.s @1
- 0xFFFFFFFF, // dc.l -1
- 0x205F, // @1 movea.l (a7)+, a0
- 0x2050, // movea.l (a0), a0
- 0x4ED0, // jmp (a0),
-
- kOurWDEFSignature,
- nil
- };
-
- #pragma mark -
-
- static pascal long WDEF(short varCode, WindowPtr theWindow, short message, long param)
- {
- WindowDefUPP old_wdef_upp;
- defproc_handle dpH;
- Handle old_wdef;
- long result;
- SInt8 state;
-
- //
- // set up to call the old WDEF. Note that we call NewRoutineDescriptor() which
- // allocates memory and may fail, but the truth is that if that would fail
- // here, worse things are about to happen (or may already have happened)!
- //
-
- dpH = (defproc_handle)((WindowPeek)theWindow)->windowDefProc;
- old_wdef = (**dpH).old_wdef;
-
- state = HGetState(old_wdef);
- HLock(old_wdef);
- old_wdef_upp = NewRoutineDescriptor((ProcPtr)*old_wdef, uppWindowDefProcInfo, kM68kISA);
- result = CallWindowDefProc(old_wdef_upp, varCode, theWindow, message, param);
- HSetState(old_wdef, state);
-
- DisposeRoutineDescriptor(old_wdef_upp);
-
- if (message == kWindowMsgCalculateShape)
- {
- WindowPeek wp = (WindowPeek)theWindow;
- RgnHandle new_struct;
-
- new_struct = NewRgn();
-
- if ((gTearRgn != nil) && (new_struct != nil))
- {
- Point struc_center;
- Point tear_center;
-
- Rect struc_box;
- Rect tear_box;
-
- struc_box = (**wp->strucRgn).rgnBBox;
- struc_center.h = (struc_box.right + struc_box.left) / 2;
- struc_center.v = (struc_box.bottom + struc_box.top) / 2;
-
- tear_box = (**gTearRgn).rgnBBox;
- tear_center.h = (tear_box.right + tear_box.left) / 2;
- tear_center.v = (tear_box.bottom + tear_box.top) / 2;
-
- OffsetRgn(gTearRgn,
- struc_center.h - tear_center.h,
- struc_center.v - tear_center.v);
-
- DiffRgn(wp->strucRgn, gTearRgn, new_struct);
-
- // we should probably not do this if the result would be empty!
- if (! EmptyRgn(new_struct))
- CopyRgn(new_struct, wp->strucRgn);
-
- // punch it out of the content region too
- DiffRgn(wp->contRgn, gTearRgn, new_struct);
- if (! EmptyRgn(new_struct))
- CopyRgn(new_struct, wp->contRgn);
- }
-
- if (new_struct != nil)
- DisposeRgn(new_struct);
- }
-
- return result;
- }
-
- #pragma mark -
- #pragma mark -
-
- void FixUpWDEF(WindowRef w)
- {
- WindowPeek wp = (WindowPeek)(w);
- defproc_handle wdef_h = (defproc_handle)wp->windowDefProc;
-
- if ((**wdef_h).signature != kOurWDEFSignature)
- {
- defproc_handle new_wdef = (defproc_handle)NewHandleClear(sizeof(defproc));
-
- if (new_wdef != nil)
- {
- WindowDefUPP upp = NewWindowDefProc(WDEF);
-
- (**new_wdef) = default_dp;
- (**new_wdef).addr = (long)upp;
- (**new_wdef).old_wdef = wp->windowDefProc;
-
- wp->windowDefProc = (Handle)new_wdef;
- }
- else
- {
- // boy, are we surprised!
- }
- }
- }
-